// (C) 2022 Intel Corporation. All rights reserved.
// Your use of Intel Corporation's design tools, logic functions and other 
// software and tools, and its AMPP partner logic functions, and any output 
// files from any of the foregoing (including device programming or simulation 
// files), and any associated documentation or information are expressly subject 
// to the terms and conditions of the Intel Program License Subscription 
// Agreement, Intel FPGA IP License Agreement, or other applicable 
// license agreement, including, without limitation, that your use is for the 
// sole purpose of programming logic devices manufactured by Intel and sold by 
// Intel or its authorized distributors.  Please refer to the applicable 
// agreement for further details.

module RSU_WRAPPER
    #(
        parameter FwRevision  = 16'h10CF, 
        parameter DeviceAddr  = 8'hAC,    
        parameter DeviceType  = 16'h11AD, 
        parameter SupportMode = 8'h05    
    )
(
    input           Clock,
    input           PllLocked,
    input           RSU_Hide,
    output reg      Reset_N,  //This reset is delay version of pll_locked
    input           LockPin,
	 input           I2C_CRC_Error,
    
    //i2c_slave avmm intf
    input  [15: 0]  avmm_address,      //Write/Read Address for writing to registers
    input  [15: 0]  avmm_writedata,    //Write Data for writing to registers
    input           avmm_write,        //Write Enable for marking Address and Data as valid to write
    input           avmm_read, 
    output          avmm_readvalid,
    output [15: 0]  avmm_readdata,     //Read Data for reading from registers  

    //expose flash ctrl&data avmm intf out
    output          avmm_csr_addr,          
    output          avmm_csr_read,            
    output [31: 0]  avmm_csr_writedata,        
    output          avmm_csr_write,            
    input  [31: 0]  avmm_csr_readdata,      
    output [31: 0]  avmm_data_addr,          
    output          avmm_data_read,            
    output [31: 0]  avmm_data_writedata,        
    output          avmm_data_write,            
    input  [31: 0]  avmm_data_readdata,           
    input           avmm_data_waitrequest,          
    input           avmm_data_readdatavalid,          
    output [ 6: 0]  avmm_data_burstcount         
);

reg  [23: 0] PowerUpResetCnt;          //Power up reset counter
reg          PowerUpReset;             //Power up reset
reg          ResetSync01;              //Reset synchronizer
reg          RuResetSync01;            //Reset synchronizer for remote update reset
reg          RuReset;                  //Reset for Remote Update logic

`ifdef SIMULATION
localparam   T_PWRUP_RST_DEL           =  8'h33;
`else
localparam   T_PWRUP_RST_DEL           =  24'h333333;
`endif


//Reset counter to hold the board in reset after a startup for a brief time
always @(posedge Clock)
begin
  if(!PllLocked)
    PowerUpResetCnt <= 24'b0;
  else if(PowerUpResetCnt < T_PWRUP_RST_DEL)
    PowerUpResetCnt <= PowerUpResetCnt + 24'd1;
  else
    PowerUpResetCnt <= PowerUpResetCnt;
end

//Register reset signal - hold until counter completes after Lock
always @(posedge Clock)
begin
  if(PowerUpResetCnt < T_PWRUP_RST_DEL)
    PowerUpReset  <= 1'b1;
  else
    PowerUpReset  <= 1'b0;
end

//Generate reset signal and synchronize to our domain (in case it doesn't start that way)
always @(posedge Clock)
begin
  ResetSync01 <= PowerUpReset;
  Reset_N     <= ~ResetSync01;
end

//Create special Remote Update reset that does not have a delay, so it can work while chip is in reset
always @(posedge Clock)
begin
  RuResetSync01 <= !PllLocked;
  RuReset       <= RuResetSync01;
end



//I2C/RSU system. Contains I2C slave state machine and Max10 flash module.

RSU_TOP 
    #(
        .FwRevision   ( FwRevision  ),
        .DeviceAddr   ( DeviceAddr  ),
        .DeviceType   ( DeviceType  ),
        .SupportMode  ( SupportMode )
    )
i2c_rsu    
(
    .Clock                   ( Clock                   ),
    .RuReset                 ( RSU_Hide |  RuReset     ),
    .Reset                   (  RSU_Hide |  ~Reset_N   ),
    .LockPin                 ( LockPin                 ),
    .I2C_CRC_Error           (I2C_CRC_Error            ),
    //flash avmm intf
    .avmm_csr_addr           ( avmm_csr_addr           ),
    .avmm_csr_read           ( avmm_csr_read           ),
    .avmm_csr_writedata      ( avmm_csr_writedata      ),
    .avmm_csr_write          ( avmm_csr_write          ),
    .avmm_csr_readdata       ( avmm_csr_readdata       ),
    .avmm_data_addr          ( avmm_data_addr          ),
    .avmm_data_read          ( avmm_data_read          ),
    .avmm_data_writedata     ( avmm_data_writedata     ),
    .avmm_data_write         ( avmm_data_write         ),
    .avmm_data_readdata      ( avmm_data_readdata      ),
    .avmm_data_waitrequest   ( avmm_data_waitrequest   ),
    .avmm_data_readdatavalid ( avmm_data_readdatavalid ),
    .avmm_data_burstcount    ( avmm_data_burstcount    ),
    //i2C slave avmm intf
    .avmm_address            ( avmm_address            ),            
    .avmm_writedata          ( avmm_writedata          ),          
    .avmm_write              ( avmm_write              ),              
    .avmm_read               ( avmm_read               ),               
    .avmm_readvalid          ( avmm_readvalid          ),
    .avmm_readdata           ( avmm_readdata           )  
);

endmodule